#pragma once

/**
 * @file SeanNetwork.h
 * @brief SeanNetwork库的总头文件
 * 
 * 包含所有SeanNetwork库的公共接口，
 * 使用者仅需包含此文件即可使用完整的SeanNetwork功能。
 * 
 * @author Sean
 * @date 2025-03-15
 */

// 基础定义
#include "NetworkTypes.h"
#include "NetworkError.h"
#include "NetworkMessage.h"

// 核心组件
#include "NetworkClient.h"
#include "NetworkServer.h"
#include "NetworkManager.h"

// 消息处理
#include "IMessageHandler.h"
#include "DefaultMessageHandler.h"

// 网络通道
#include "INetworkChannel.h"
#include "TcpChannel.h"
#include "KcpChannel.h"
#include "NetworkChannelFactory.h"

// 工具类
#include "Serializer.h"
#include "TimerManager.h"
#include "MessagePool.h"

// 日志系统
#include "Logger.h"

/**
 * @namespace SeanNetwork
 * @brief SeanNetwork库的主命名空间
 * 
 * 包含所有SeanNetwork库的类、结构体、枚举和函数。
 */
namespace SeanNetwork {

/**
 * @enum LogLevel
 * @brief 日志级别枚举
 */
enum class LogLevel {
    Debug,      ///< 调试信息，仅开发时使用
    Info,       ///< 一般信息，程序正常运行时的状态
    Warning,    ///< 警告信息，可能存在问题但不影响程序运行
    Error,      ///< 错误信息，程序出错但可以继续运行
    Fatal       ///< 致命错误，程序无法继续运行
};

/**
 * @struct NetworkConfig
 * @brief 网络库配置选项
 */
struct NetworkConfig {
    // 是否开启自动重连
    bool EnableAutoReconnect = true;
    
    // 是否启用消息池
    bool EnableMessagePool = true;
    
    // TCP发送超时（毫秒）
    uint32_t TcpSendTimeout = 5000;
    
    // TCP接收超时（毫秒）
    uint32_t TcpReceiveTimeout = 5000;
    
    // KCP每次更新间隔（毫秒）
    uint32_t KcpUpdateInterval = 10;
    
    // KCP是否启用快速重传
    bool KcpFastResend = true;
    
    // KCP窗口大小 (32 for LAN, 128 for WAN)
    uint32_t KcpWindowSize = 128;
    
    // KCP最大传输单元
    uint32_t KcpMtu = 1400;
    
    // 日志级别
    LogLevel LogLevel = LogLevel::Info;
    
    // 是否将日志输出到文件
    bool LogToFile = false;
    
    // 日志文件路径，为空时使用默认路径
    std::string LogFilePath = "";
};

/**
 * @brief 初始化SeanNetwork库
 * 
 * 在使用SeanNetwork库之前必须调用此函数进行初始化。
 * 此函数会初始化全局资源，设置日志系统。
 * 
 * @param logLevel 日志级别，默认为Info
 * @return 初始化是否成功
 */
inline bool Initialize(LogLevel logLevel = LogLevel::Info) {
    // 初始化日志系统
    return Logger::GetInstance().Initialize(logLevel);
}

/**
 * @brief 使用详细配置初始化SeanNetwork库
 * 
 * 使用NetworkConfig结构体提供更详细的配置选项。
 * 
 * @param config 网络配置
 * @return 初始化是否成功
 */
inline bool InitializeWithConfig(const NetworkConfig& config) {
    // 初始化日志系统
    bool success = Logger::GetInstance().Initialize(config.LogLevel, config.LogToFile, config.LogFilePath);
    
    if (success) {
        // 记录初始化配置
        LOG_INFO("SeanNetwork 初始化完成");
        LOG_DEBUG("配置: KCP更新间隔=" + std::to_string(config.KcpUpdateInterval) + 
                 "ms, KCP窗口大小=" + std::to_string(config.KcpWindowSize));
    }
    
    return success;
}

/**
 * @brief 关闭SeanNetwork库
 * 
 * 在程序退出前调用此函数释放所有资源。
 */
inline void Shutdown() {
    // 关闭日志系统
    Logger::GetInstance().Shutdown();
}

/**
 * @brief 设置日志级别
 * 
 * @param level 日志级别
 */
inline void SetLogLevel(LogLevel level) {
    Logger::GetInstance().SetLogLevel(level);
}

/**
 * @brief 创建网络客户端
 * 
 * 创建一个网络客户端用于连接服务器。
 * 
 * @param protocol 连接协议（TCP或KCP）
 * @return 网络客户端实例
 */
inline std::shared_ptr<NetworkClient> CreateClient(ProtocolType protocol = ProtocolType::TCP) {
    LOG_DEBUG("创建网络客户端: 协议=" + std::string(protocol == ProtocolType::TCP ? "TCP" : "KCP"));
    return std::make_shared<NetworkClient>(protocol);
}

/**
 * @brief 创建网络服务器
 * 
 * 创建一个网络服务器监听连接请求。
 * 
 * @param protocol 连接协议（TCP或KCP）
 * @return 网络服务器实例
 */
inline std::shared_ptr<NetworkServer> CreateServer(ProtocolType protocol = ProtocolType::TCP) {
    LOG_DEBUG("创建网络服务器: 协议=" + std::string(protocol == ProtocolType::TCP ? "TCP" : "KCP"));
    return std::make_shared<NetworkServer>(protocol);
}

/**
 * @brief 获取SeanNetwork库版本号
 * 
 * @return 版本号字符串，格式为"主版本.次版本.修订版本"
 */
inline const char* GetVersion() {
    return "1.1.0";
}

/**
 * @brief 创建网络管理器实例
 * 
 * 工厂函数，创建并返回一个网络管理器智能指针，
 * 网络管理器提供比单独的客户端或服务器更复杂的功能。
 * 
 * @return NetworkManager的智能指针
 */
inline std::unique_ptr<NetworkManager> CreateNetworkManager() {
    return std::make_unique<NetworkManager>();
}

/**
 * @brief 获取网络错误描述
 * 
 * 根据错误码返回对应的错误描述文本。
 * 
 * @param errorCode 错误码
 * @return 错误描述字符串
 */
inline const char* GetErrorString(NetworkErrorCode errorCode) {
    switch (errorCode) {
        case NetworkErrorCode::Success:
            return "Success";
        case NetworkErrorCode::InvalidArgument:
            return "Invalid argument";
        case NetworkErrorCode::ConnectionFailed:
            return "Connection failed";
        case NetworkErrorCode::ConnectionClosed:
            return "Connection closed";
        case NetworkErrorCode::SendFailed:
            return "Failed to send data";
        case NetworkErrorCode::ReceiveFailed:
            return "Failed to receive data";
        case NetworkErrorCode::Timeout:
            return "Operation timeout";
        case NetworkErrorCode::NotInitialized:
            return "Not initialized";
        case NetworkErrorCode::AlreadyInitialized:
            return "Already initialized";
        case NetworkErrorCode::OutOfMemory:
            return "Out of memory";
        case NetworkErrorCode::InternalError:
            return "Internal error";
        default:
            return "Unknown error";
    }
}

/**
 * @brief 获取内存池统计信息
 * 
 * 返回内存池的使用情况统计
 * 
 * @return 内存池统计字符串
 */
inline std::string GetMemoryPoolStats() {
    LOG_DEBUG("获取内存池统计信息");
    return MemoryPoolAllocator<char>::GetGlobalMemoryPool()->GetStats();
}

} // namespace SeanNetwork
